package com.statistics.util;

import lombok.AllArgsConstructor;
import lombok.Getter;
import org.apache.poi.ss.usermodel.*;
import org.apache.poi.xssf.usermodel.XSSFWorkbook;
import org.springframework.core.io.ClassPathResource;

import javax.servlet.http.HttpServletResponse;
import java.io.InputStream;
import java.util.Arrays;
import java.util.List;
import java.util.Map;

public class EducationExportUtils {

    public static void exportWithTemplate(HttpServletResponse response,
                                          List<?> data, String fileName, int type) throws Exception {
        // 设置响应头
        AchExportUtils.setResponse(response, fileName);
        // 加载模板文件
        ClassPathResource resource = new ClassPathResource("/templates/" + fileName + ".xlsx");
        try (InputStream inputStream = resource.getInputStream();
             Workbook workbook = new XSSFWorkbook(inputStream)) {

            Sheet sheet = workbook.getSheetAt(0);

            if (type == 5) {
                // 科技成果
                insertListData(sheet, data);
            } else {
                // 处理动态列表数据
                insertListData(sheet, data, AchExportUtils.createTotalStyle(workbook), type);
            }

            // 写入输出流
            workbook.write(response.getOutputStream());
        }
    }

    private static void insertListData(Sheet sheet, List<?> listData) {
        int startRow = 10;
        for (int i = 0; i < listData.size(); i++) {
            Row row = sheet.getRow(startRow + i);
            Map<String, Object> item = (Map<String, Object>) listData.get(i);
            for (ColumnConfig config : SCIENCE_ACHIEVEMENT) {
                Object value = item.getOrDefault(config.getKey(), config.getDefaultValue());
                row.getCell(config.getColumnIndex()).setCellValue(value.toString());
            }
        }
    }

    private static void insertListData(Sheet sheet, List<?> listData, CellStyle style, int type) {
        int startRow = getStartRow(sheet);
        if (startRow == -1) return;

        // 删除模板中的占位行
        Row templateRow = sheet.getRow(startRow);
        sheet.removeRow(templateRow);
        List<ColumnConfig> configList = null;
        switch (type) {
            case 1:
                configList = RES_PERSON;
                break;
            case 2:
                configList = ACTIVITY_UNIT;
                break;
            case 3:
                configList = SCIENCE_PROJECT;
                break;
            case 6:
                configList = PUBLISH_BOOK;
                break;
            case 7:
                configList = SCIENCE_HONOR;
                break;
        }

        // 插入列表数据
        for (int i = 0; i < listData.size(); i++) {
            Row newRow = sheet.createRow(startRow + i);
            createCellWithStyle(newRow, 0, i + 1, style);

            // 获取数据项（提前转换减少重复操作）
            Map<String, Object> item = (Map<String, Object>) listData.get(i);

            // 动态处理数据列
            if (configList != null) {
                for (ColumnConfig config : configList) {
                    Object value = item.getOrDefault(config.getKey(), config.getDefaultValue());
                    createCellWithStyle(newRow, config.getColumnIndex(), value, style);
                }
            }
        }
    }

    private static int getStartRow(Sheet sheet) {
        // 查找列表起始行${list}
        int startRow = -1;
        for (Row row : sheet) {
            for (Cell cell : row) {
                if (cell.getCellType() == CellType.STRING &&
                        cell.getStringCellValue().equals("${list}")) {
                    startRow = row.getRowNum();
                    break;
                }
            }
            if (startRow != -1) break;
        }
        return startRow;
    }

    private static void createCellWithStyle(Row row, int columnIndex, Object value, CellStyle style) {
        Cell cell = row.createCell(columnIndex);
        if (value != null) {
            cell.setCellValue(value.toString());
        }
        cell.setCellStyle(style);
    }

    @AllArgsConstructor
    @Getter
    static class ColumnConfig {
        private final int columnIndex;
        private final String key;
        private final Object defaultValue;
    }

    // 定义科技人力配置
    private static final List<ColumnConfig> RES_PERSON = Arrays.asList(
            new ColumnConfig(1, "name", ""),
            new ColumnConfig(2, "sex", ""),
            new ColumnConfig(3, "birthday", ""),
            new ColumnConfig(4, "eduLevel", ""),
            new ColumnConfig(5, "titleRank", ""),
            new ColumnConfig(7, "subject", ""),
            new ColumnConfig(9, "idCard", "")
    );

    // 定义科技活动机构情况配置
    private static final List<ColumnConfig> ACTIVITY_UNIT = Arrays.asList(
            new ColumnConfig(1, "name", ""),
            new ColumnConfig(2, "code", ""),
            new ColumnConfig(3, "unitType", ""),
            new ColumnConfig(4, "unitClass", ""),
            new ColumnConfig(5, "subject", ""),
            new ColumnConfig(6, "form", ""),
            new ColumnConfig(7, "personNums", ""),
            new ColumnConfig(8, "doctorNum", ""),
            new ColumnConfig(9, "masterNum", ""),
            new ColumnConfig(10, "personSum", ""),
            new ColumnConfig(11, "seniorNum", ""),
            new ColumnConfig(12, "intermediateNum", ""),
            new ColumnConfig(13, "primaryNum", ""),
            new ColumnConfig(14, "othersNum", ""),
            new ColumnConfig(15, "graduateStuNum", ""),
            new ColumnConfig(16, "curYearPay", ""),
            new ColumnConfig(17, "curyearRdPay", ""),
            new ColumnConfig(18, "chargedProNum", ""),
            new ColumnConfig(19, "assetsValue", ""),
            new ColumnConfig(20, "originalCost", ""),
            new ColumnConfig(21, "importCost", ""),
            new ColumnConfig(22, "gmjjhy", "")
    );

    // 定义科技项目(课题)情况配置
    private static final List<ColumnConfig> SCIENCE_PROJECT = Arrays.asList(
            new ColumnConfig(1, "name", ""),
            new ColumnConfig(2, "authorizeDate", ""),
            new ColumnConfig(3, "incomeSum", ""),
            new ColumnConfig(4, "outSum", ""),
            new ColumnConfig(5, "memberCount", ""),
            new ColumnConfig(6, "sexCount", ""),
            new ColumnConfig(7, "seniorNum", ""),
            new ColumnConfig(8, "intermediateNum", ""),
            new ColumnConfig(9, "primaryNum", ""),
            new ColumnConfig(10, "otherNum", ""),
            new ColumnConfig(11, "doctorYear", ""),
            new ColumnConfig(12, "participants", ""),
            new ColumnConfig(13, "doctorNum", ""),
            new ColumnConfig(14, "masterNum", ""),
            new ColumnConfig(15, "subject", ""),
            new ColumnConfig(16, "researchClass", ""),
            new ColumnConfig(17, "projectSouce", ""),
            new ColumnConfig(18, "form", ""),
            new ColumnConfig(19, "cooperate", ""),
            new ColumnConfig(20, "gmjjhy", ""),
            new ColumnConfig(21, "societyTarger", ""),
            new ColumnConfig(22, "flag", "")
    );

    // 定义科技成果情况表配置
    private static final List<ColumnConfig> SCIENCE_ACHIEVEMENT = Arrays.asList(
            new ColumnConfig(2, "total", ""),
            new ColumnConfig(3, "publishRange", ""),
            new ColumnConfig(4, "scie", ""),
            new ColumnConfig(5, "ei", ""),
            new ColumnConfig(6, "cpcis", "")
    );

    // 定义出版科技著作情况配置
    private static final List<ColumnConfig> PUBLISH_BOOK = Arrays.asList(
            new ColumnConfig(1, "name", ""),
            new ColumnConfig(2, "firstAuthorName", ""),
            new ColumnConfig(3, "authorOrder", ""),
            new ColumnConfig(4, "wordNumber", ""),
            new ColumnConfig(5, "writeNumber", ""),
            new ColumnConfig(6, "type", ""),
            new ColumnConfig(7, "publishUnit", ""),
            new ColumnConfig(8, "publishAddress", ""),
            new ColumnConfig(9, "isbn", ""),
            new ColumnConfig(10, "publishDate", ""),
            new ColumnConfig(11, "subject", "")
    );

    // 定义科技成果奖励情况配置
    private static final List<ColumnConfig> SCIENCE_HONOR = Arrays.asList(
            new ColumnConfig(1, "productName", ""),
            new ColumnConfig(2, "unitOrder", ""),
            new ColumnConfig(3, "honorType", ""),
            new ColumnConfig(4, "name", ""),
            new ColumnConfig(5, "honorGrade", ""),
            new ColumnConfig(6, "subject", "")
    );
}